home *** CD-ROM | disk | FTP | other *** search
/ Technotools / Technotools (Chestnut CD-ROM)(1993).ISO / lang_c / cug106 / mouse.c < prev    next >
Text File  |  1984-06-14  |  5KB  |  290 lines

  1. /*
  2.     'mouse' interperter
  3.  
  4.     Adapted from a Pascal program in Byte (July 79)
  5.  
  6.     *** Macro expansions do not work properly ***
  7.  
  8.     This was done less as something useful in its
  9.     own right than to get a clue how easily Pascal
  10.     is translatable into C.        H.R.M.
  11.  
  12. */
  13.  
  14. #define MACRO 0
  15. #define PARAM 1
  16. #define LOOP 2
  17.  
  18. #define TAGTYPE char    /* set of (MACRO,PARAM,LOOP) */
  19.  
  20.  
  21. /*        --- Global variables ---        */
  22.  
  23.     int trace;
  24.     char prog[500];            /* program buffer */
  25.     int definitions[26];        /* macro definitions */
  26.     int calstack[20];        /* macro nesting stack */
  27.     struct frametype {
  28.         TAGTYPE tag;
  29.         int pos,off;
  30.         }  stack[20];
  31.     int data[260];
  32.     char ch;
  33.     int cal,chpos,level,offset,parnum,parbal,temp;
  34.  
  35.     char file[134];    /* input file buffer structure */
  36.     int fd;        /* file descriptor */
  37.  
  38.  
  39.  
  40. main(argc,argv)
  41.     int argc;
  42.     char *argv[];
  43.     {
  44.  
  45.     if( (fd = fopen(argv[1],file)) < 0 )
  46.       exit(printf("No such file: %s\n",argv[1]));
  47.     if( *argv[2] == 'T' )
  48.       trace = 1;
  49.     else
  50.       trace = 0;
  51.     load();
  52.     chpos = level = offset = cal = 0;
  53.     do {
  54.       getchr();
  55.       if( ch == ']' || ch == '$' || isspace(ch) )
  56.         ;
  57.       else if( isdigit(ch) ) {
  58.         temp = 0;
  59.         while( isdigit( ch ) ) {
  60.           temp = temp*10 + val(ch);
  61.           getchr();
  62.           }
  63.         pushcal(temp);
  64.         ungetchr();
  65.         }
  66.       else if( isalpha( ch ) )
  67.         pushcal( offset + num(ch) );
  68.       else
  69.         switch(ch) {
  70.  
  71.           case '?':    scanf("%d",&temp);
  72.             pushcal(temp);
  73.             break;
  74.  
  75.           case '!':    printf("%d",popcal());
  76.             break;
  77.  
  78.           case '+':    pushcal(popcal() + popcal());
  79.             break;
  80.  
  81.           case '-':    pushcal( - popcal() + popcal() );
  82.             break;
  83.  
  84.           case '*':    pushcal( popcal() * popcal() );
  85.             break;
  86.  
  87.           case '/':    temp = popcal();
  88.             pushcal(popcal() / temp);
  89.             break;
  90.  
  91.           case '.':    pushcal(data[popcal()]);
  92.             break;
  93.  
  94.           case '=':    temp = popcal();
  95.             data[popcal()] = temp;
  96.             break;
  97.  
  98.           case '"':    while(getchr() != '"' )
  99.               if( ch == '!' )
  100.                 putchar('\n');
  101.               else
  102.                 putchar(ch);
  103.             break;
  104.  
  105.           case '[':    if( popcal() <= 0 )
  106.               skip('[',']');
  107.             break;
  108.  
  109.           case '(':    push(LOOP);
  110.             break;
  111.  
  112.           case '^':    if( popcal() <= 0 ) {
  113.               pop();
  114.               skip('(',')');
  115.               }
  116.             break;
  117.  
  118.           case ')':    chpos = stack[level].pos;
  119.             break;
  120.  
  121.           case '#':    getchr();
  122.             if( definitions[num(ch)] > 0 ) {
  123.               push(MACRO);
  124.               chpos = definitions[num(ch)];
  125.               offset += 26;
  126.               }
  127.             else
  128.               skip('#',';');
  129.             break;
  130.  
  131.           case '@':    pop();
  132.             skip('#',';');
  133.             break;
  134.  
  135.           case '%':    getchr();
  136.             parnum = num(ch);
  137.             push(PARAM);
  138.             parbal = 1;
  139.             temp = level;
  140.             do {
  141.               switch( stack[--temp].tag ) {
  142.  
  143.                 case PARAM:
  144.                 case MACRO:    parbal--;
  145.                     break;
  146.  
  147.                 case LOOP:    break;
  148.                 }
  149.               } while( parbal != 0 );
  150.             chpos = stack[temp].pos;
  151.             offset = stack[temp].off;
  152.             do {
  153.               getchr();
  154.               if( ch == '#' ) {
  155.                 skip('#',';');
  156.                 getchr();
  157.                 }
  158.               if( ch == ',' )
  159.                 parnum--;
  160.               } while( parnum != 0 && ch != ';' );
  161.             if( ch == ';' )
  162.               pop();
  163.             break;
  164.  
  165.           case ',':
  166.           case ';':    pop();
  167.             break;
  168.  
  169.           }
  170.       } while( ch != '$');
  171.     }
  172.  
  173.  
  174. num(chr)
  175.     char chr;
  176.     {
  177.     return tolower(chr) - 'a' + 1;
  178.     }
  179.  
  180.  
  181.  
  182. val(chr)
  183.     char chr;
  184.     {
  185.     return tolower(chr) - '0';
  186.     }
  187.  
  188.  
  189.  
  190. getchr()
  191.     {
  192.     if(trace) {    /* --- debug tracing selected --- */
  193.       putchar('\n');
  194.       putchar('\\');
  195.       putchar(prog[++chpos]);
  196.       putchar('\\');
  197.       return (ch = prog[chpos]);
  198.       }
  199.     else
  200.       return (ch = prog[++chpos]);
  201.     }
  202.  
  203.  
  204.  
  205. pushcal(datum)
  206.     int datum;
  207.     {
  208.     return (calstack[++cal] = datum);
  209.     }
  210.  
  211.  
  212.  
  213. popcal()
  214.     {
  215.     return (calstack[cal--]);
  216.     }
  217.  
  218.  
  219.  
  220. push(tagval)
  221.     TAGTYPE tagval;
  222.     {
  223.  
  224.     level++;
  225.     stack[level].tag = tagval;
  226.     stack[level].pos = chpos;
  227.     stack[level].off = offset;
  228.     }
  229.  
  230.  
  231.  
  232. pop()
  233.     {
  234.  
  235.     chpos = stack[level].pos;
  236.     offset = stack[level].off;
  237.     return --level;
  238.     }
  239.  
  240.  
  241.  
  242.  
  243. skip(lch,rch)
  244.     char lch,rch;
  245.     {
  246.     int cnt;
  247.  
  248.     cnt = 1;
  249.     while( cnt ) {
  250.       getchr();
  251.       if( ch == lch )
  252.         cnt++;
  253.       else if( ch == rch )
  254.         cnt--;
  255.       else
  256.         ;
  257.       }
  258.     }
  259.  
  260.  
  261.  
  262.  
  263. load()
  264.     {
  265.     char this,last;
  266.     int charnum;
  267.  
  268.     for(charnum = 1; charnum <= 26; charnum++)
  269.       definitions[charnum] = 0;
  270.     charnum =0;
  271.     this = ' ';
  272.     while( ! ( last == '$' && this == '$' ) ) {
  273.       last = this;
  274.       this = getc(file);
  275.       prog[++charnum] = this;
  276.       if( last == '$' && isalpha(this) )
  277.         definitions[num(this)] = charnum;
  278.       }
  279.     }
  280.  
  281.  
  282.  
  283. ungetchr()
  284.     {
  285.     chpos--;
  286.     }
  287.  
  288.  
  289.  
  290.